Use native file system observer for livereload#73
Use native file system observer for livereload#73ericchansen wants to merge 1 commit intoProperDocs:masterfrom
Conversation
Replace the hardcoded PollingObserver with watchdog's platform-default Observer, which automatically selects the best native backend per platform (inotify on Linux, FSEvents on macOS, ReadDirectoryChangesW on Windows). This fixes live reload on Linux and WSL2, where PollingObserver silently fails to detect file changes on ext4 filesystems. To preserve symlink support that PollingObserver provided via stat(), the watch() method now resolves symlink paths with os.path.realpath() and adds filtered watches for symlink targets outside the watched tree. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
1026eee to
7384546
Compare
|
Thanks Which considerations were made so that the intentional revert of native observers is not applicable anymore? And have you seen the code how it was prior to the revert? Seems we have different implementations that both catch a lot of pitfalls, but does this one catch all of the same pitfalls and more? |
|
Wont it be better if this PR moved to |
Closing — wrong root causeAfter investigating further, the livereload issue I experienced was not caused by I confirmed @oprypin — you were right to ask about the 2021 revert. Native observers still fail on 9p/NFS/Docker-mounted filesystems (confirmed: 0/5 detections on @baseplate-admin — Sorry for the noise. |
Summary
Replace the hardcoded
PollingObserverwith watchdog's platform-defaultObserverin the livereload server. This fixes live reload on Linux and WSL2, wherePollingObserversilently fails to detect file changes on ext4 filesystems.Problem
properdocs servedoes not live-reload on WSL2 (and potentially other Linux configurations). The root cause is thatPollingObserveruses periodicstat()calls, which don't reliably reflect file changes on WSL2's ext4 filesystem. The browser never reloads, even thoughinotifywaitand watchdog's nativeInotifyObserverboth detect changes instantly.Related upstream: mkdocs/mkdocs#4081
Fix
Use
watchdog.observers.Observerinstead ofwatchdog.observers.polling.PollingObserver. TheObserverclass is watchdog's documented public API and auto-selects the best backend per platform:InotifyObserver(kernel inotify -- instant, zero CPU overhead)FSEventsObserver(instant)WindowsApiObserver(instant)PollingObserver(if native observer unavailable)Symlink support
Native observers (inotify, FSEvents) don't follow symlinks the way
stat()-based polling does. To preserve the existing symlink behavior,watch()now:os.path.realpath()so symlinked directories are watched at their real location.unwatch().Changes
properdocs/livereload/__init__.pyPollingObserverwithObserver, add symlink-following logicTesting
test_watches_direct_symlinks,test_watches_through_symlinks,test_watches_through_relative_symlinks)hatch run allpasses (style, types, unit tests, integration tests)